/**
 * @Author       : Mo 2427995270@qq.com
 * @Date         : 2025-06-10 16:21:41
 * @LastEditTime : 2025-08-19 22:50:06
 * @FilePath     : \hal_driver\hal_systick.c
 * @Description  : systick抽象层 用于在裸机时实现定时任务
 * @Version      : V1.0
 * @History      :
 * @Note         :
 */
/***************************************Includes***********************************/
#include "hal_systick.h"


/************************************Private Macros********************************/
// #define


/**********************************Private Statement*******************************/


/***********************************Public Variables*******************************/



/**********************************Private Variables*******************************/

static uint32_t tick_cnt;
static uint32_t tick_ms;
static systick_hal_t *tick_head;


/**********************************Public Functions********************************/


/**
 * @brief 初始化tick节拍时间
 * @param  tick_ms          每 tick_ms 调用systick_hal_increase
 * @note 建议tick_ms为1ms 时间长了一些对象的定时任务有偏差
 */
void systick_hal_init(uint32_t ms) {
    tick_ms = ms;
}

/**
 * @brief 节拍增加 需在systick中断中调用或在定时器中断中调用
 * @note null
 */
void systick_hal_increase(void) {
    tick_cnt += tick_ms;
    systick_hal_t *node = tick_head;
    while (node) {
        if (node->timer_en) {
            if (node->start <= tick_cnt) {
                if ((tick_cnt - node->start) >= node->time) {
                    node->start = tick_cnt;
                    node->cb(node);
                }
            } else {
                if ((UINT32_MAX - node->start + tick_cnt) >= node->time) {
                    node->start = tick_cnt;
                    node->cb(node);
                }
            }
        }
        node = node->next;
    }
}
/**
 * @brief 添加定时器
 * @param  sht              句柄
 * @param  time_ms          定时时长
 * @param  name             定时器名
 * @param  cb               定时到时回调函数
 * @param  arg              用户参数
 * @return int 0成功 -1未初始化
 * @note null
 */
int systick_hal_add_timer(systick_hal_t *sht, uint32_t time_ms, const char *name, systick_hal_cb_t cb, void *arg) {
    if(tick_ms == 0) {
        return -1;
    }
    sht->time = time_ms;
    sht->timer_en = 0;
    sht->name = name;
    sht->cb = cb;
    sht->arg = arg;
    sht->next = (void *)0;
    if (tick_head == (void *)0) {
        tick_head = sht;
        return 0;
    }
    systick_hal_t *node = tick_head;
    while (node->next) {
        node = node->next;
    }
    node->next = sht;
    return 0;
}
/**
 * @brief 删除定时器
 * @param  sht              句柄
 * @note null
 */
void systick_hal_remove_timer(systick_hal_t *sht) {
    if (sht == tick_head) {
        tick_head = tick_head->next;
        return;
    }
    systick_hal_t *node = tick_head;
    while (node->next) {
        if (node->next == sht) {
            node->next = sht->next;
            sht->cb = 0;
            sht->arg = 0;
            sht->timer_en = 0;
            sht->time = 0;
            return;
        }
        node = node->next;
    }
}
/**
 * @brief 启动定时器
 * @param  sht              句柄
 * @note null
 */
void systick_hal_start_timer(systick_hal_t *sht) {
    sht->timer_en = 1;
    sht->start = tick_cnt;
}
/**
 * @brief 停止定时器
 * @param  sht              句柄
 * @note null
 */
void systick_hal_stop_timer(systick_hal_t *sht) {
    sht->timer_en = 0;
}
/**
 * @brief 重置定时器计时
 * @param  sht              句柄
 * @note null
 */
void systick_hal_reset_timer(systick_hal_t *sht) {
    sht->timer_en = 1;
    sht->start = tick_cnt;
}


/**********************************Private Functions*******************************/


/* [] END OF FILE */
